package com.zxy.zxyrpc.serializer;

import com.esotericsoftware.kryo.Kryo;
import com.esotericsoftware.kryo.io.Input;
import com.esotericsoftware.kryo.io.Output;

import java.io.*;

/**
 * Kryo 序列化器（线程不安全）
 *
 * @author zxy
 * @since 2025/5/11
 **/

public class KryoSerializer implements Serializer {

    /**
     * kryo 线程线程不安全，使用 ThreadLocal 保证每个线程只有一个kryo（静态可能更好）
     */
    private static final ThreadLocal<Kryo> KRYO_THREAD_LOCAL = ThreadLocal.withInitial(()->{
        Kryo kryo = new Kryo();
        // 设置动态序列化和反序列化类，不提前注册所有的类（可能有安全问题）
        kryo.setRegistrationRequired(false);
        return kryo;
    });
    @Override
    public <T> byte[] serialize(T obj) throws IOException {
        try(Output output = new Output(new ByteArrayOutputStream());) {
            KRYO_THREAD_LOCAL.get().writeObject(output,obj);
            return output.toBytes();
        } finally {
            KRYO_THREAD_LOCAL.remove();
        }
    }

    @Override
    public <T> T deserialize(byte[] bytes, Class<T> type) throws IOException {
        try(Input input = new Input(new ByteArrayInputStream(bytes));) {
            return KRYO_THREAD_LOCAL.get().readObject(input, type);
        } finally {
            KRYO_THREAD_LOCAL.remove();
        }
    }
}
